package com.qjdchina.sku.biz.impl;

import java.io.IOException;
import java.util.Iterator;
import java.util.Map;

import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.NameValuePair;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpMethodParams;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.BeanCreationException;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import com.alibaba.fastjson.JSON;
import com.qjdchina.commons.result.Result;
import com.qjdchina.sku.biz.SmsRecordManager;
import com.qjdchina.sku.biz.YunpianSmsManager;
import com.qjdchina.sku.model.SmsRecord;
import com.qjdchina.sku.service.enums.SkuResultCode;

@Service
public class YunpianSmsManagerImpl implements YunpianSmsManager, InitializingBean {

    private static final Logger LOGGER = LoggerFactory.getLogger(YunpianSmsManagerImpl.class);
    
    @Autowired
    private SmsRecordManager smsRecordManager;

    /**
     * 短信发送地址
     */
    @Value("#{sku['sku.sms.yunpian.url']}")
    private String url;

    /**
     * API KEY
     */
    @Value("#{sku['sku.sms.yunpian.apiKey']}")
    private String apiKey;

    /**
     * 编码格式
     */
    private String encoding = "UTF-8";

    @Override
    public Result<String> sendWithTemplate(long tplId, Map<String, String> tplValue, String mobile) {

        HttpClient client = new HttpClient();
        NameValuePair[] nameValuePairs = new NameValuePair[4];
        nameValuePairs[0] = new NameValuePair("apikey", apiKey);
        nameValuePairs[1] = new NameValuePair("tpl_id", String.valueOf(tplId));
        nameValuePairs[2] = new NameValuePair("tpl_value", getTplValue(tplValue));
        nameValuePairs[3] = new NameValuePair("mobile", mobile);
        PostMethod method = new PostMethod(url);
        method.setRequestBody(nameValuePairs);
        HttpMethodParams param = method.getParams();
        param.setContentCharset(encoding);
        try {
            client.executeMethod(method);
            String returnJson = method.getResponseBodyAsString();

            // 解析短信回执信息
            YunpianReturn sr = JSON.parseObject(returnJson, YunpianReturn.class);

            // 记录发送短信次数
            sendSmsRecordCount(mobile);
            
            // 发送失败
            if (sr.getCode() != 0) {
                LOGGER.error("send sms fail, template id: {}, mobile: {}, error code: {}, detail: {}", tplId, mobile,
                        sr.getCode(), sr.getDetail());
                return new Result<String>(SkuResultCode.SYS_EXCEPTION);
            }

            // 成功
            return new Result<String>(sr.getDetail());

        } catch (IOException e) {
            LOGGER.error("http request error.", e);
            return new Result<String>(SkuResultCode.SYS_EXCEPTION);
        }
    }

    /**
     * 获取 对应的模板变量值
     * 
     * @param values
     * @return
     */
    private String getTplValue(Map<String, String> values) {
        boolean isFirst = true;
        StringBuilder builder = new StringBuilder();
        for (Iterator<String> keys = values.keySet().iterator(); keys.hasNext();) {
            String key = keys.next();
            if (isFirst) {
                builder.append("#").append(key).append("#").append("=").append(values.get(key));
                isFirst = false;
            } else {
                builder.append("&").append("#").append(key).append("#").append("=").append(values.get(key));
            }
        }
        return builder.toString();
    }

    @Override
    public void afterPropertiesSet() throws Exception {
        if (StringUtils.isEmpty(url)) {
            throw new BeanCreationException("field[url] is not initialized.");
        }
        if (StringUtils.isEmpty(apiKey)) {
            throw new BeanCreationException("field[apiKey] is not initialized.");
        }
    }
    
    //记录发送短信的次数
    private void sendSmsRecordCount(String mobile){
    	
    	Result<SmsRecord> result = smsRecordManager.getSmsRecordByMobile(mobile);
    	
    	//如果存在，则 更新， 不存在 则 新增
    	if (result.isSuccess()) {
			SmsRecord sms = result.getDataModel();
			sms.setId(sms.getId());
			sms.setSentCount(sms.getSentCount() + 1);
			try {
				Result<String> upRes = smsRecordManager.updateRecord(sms);
				 if (!upRes.isSuccess()) {
					 LOGGER.error(" update SmsRecord fail...");
				}
			} catch (Exception e) {
				LOGGER.error(" update SmsRecord exception.", e);
			}
			
		}else{
			SmsRecord sms = new SmsRecord();
			sms.setMobile(mobile);
			sms.setSentCount(1);
			try {
				Result<String> addRes = smsRecordManager.addRecord(sms);
				if (!addRes.isSuccess()) {
					 LOGGER.error(" add SmsRecord fail...");
				}
			} catch (Exception e) {
				LOGGER.error(" add SmsRecord exception.", e);
			}
		}
    }

    public String getUrl() {
        return url;
    }

    public void setUrl(String url) {
        this.url = url;
    }

    public String getApiKey() {
        return apiKey;
    }

    public void setApiKey(String apiKey) {
        this.apiKey = apiKey;
    }

    public String getEncoding() {
        return encoding;
    }

    public void setEncoding(String encoding) {
        this.encoding = encoding;
    }
}

class YunpianReturn {

    /**
     * 错误码
     * 
     * @see http://www.yunpian.com/api/retcode.html
     */
    private int code;

    /**
     * 错误描述
     */
    private String msg;

    /**
     * 具体错误描述或解决方法
     */
    private String detail;

    private YunpianReturnResult result;

    public int getCode() {
        return code;
    }

    public void setCode(int code) {
        this.code = code;
    }

    public String getMsg() {
        return msg;
    }

    public void setMsg(String msg) {
        this.msg = msg;
    }

    public String getDetail() {
        return detail;
    }

    public void setDetail(String detail) {
        this.detail = detail;
    }

    public YunpianReturnResult getResult() {
        return result;
    }

    public void setResult(YunpianReturnResult result) {
        this.result = result;
    }
}

class YunpianReturnResult {

    /**
     * 成功发送的短信个数
     */
    private int count;

    /**
     * 扣费条数，70个字一条，超出70个字时按每67字一条计
     */
    private int fee;

    /**
     * /短信id；群发时以该id+手机号尾号后8位作为短信id
     */
    private String sid;

    public int getCount() {
        return count;
    }

    public void setCount(int count) {
        this.count = count;
    }

    public int getFee() {
        return fee;
    }

    public void setFee(int fee) {
        this.fee = fee;
    }

    public String getSid() {
        return sid;
    }

    public void setSid(String sid) {
        this.sid = sid;
    }
}
